package jmine.tec.services.api;

import java.util.List;

import jmine.tec.di.scope.TypedScope;
import jmine.tec.services.ServicesController;

import org.springframework.transaction.TransactionDefinition;

import bancosys.tec.persist.controller.PersistenceEnabledController;

/**
 * Interface que define um servico.
 * 
 * @param <C> Tipo do controller utilizado pelo servico
 * @author Rafael Volpato
 * @created Jun 4, 2007
 */
public interface Service<C extends PersistenceEnabledController> extends Cloneable {

    /**
     * Retorna a action desse servico.
     * 
     * @return a action desse servico
     */
    ActionsEnum getAction();

    /**
     * Executa o servico
     * 
     * @throws ServiceExecutionException se ocorrer algum erro durante a execucao do servico
     */
    void execute() throws ServiceExecutionException;

    /**
     * Valida a consistencia dos dados passados para o servico.
     * 
     * @return lista de erros de validacao encontrados
     */
    List<String> validate();

    /**
     * Retorna o nome do servico.
     * 
     * @return o nome do servico
     */
    String getServiceName();

    /**
     * Retorna o controller especifico utilizado pelo servico.
     * 
     * @return controller
     * @deprecated usar o <code>@Injected</code> para injetar o controller certo
     */
    C getController();

    /**
     * Seta o controller especifico utilizado pelo servico.
     * 
     * @param controller controller
     * @deprecated usar o <code>@Injected</code> para injetar o controller certo
     */
    void setController(C controller);

    /**
     * Retorna o servicesController.
     * 
     * @return o servicesController
     */
    ServicesController getServicesController();

    /**
     * Seta o servicesController.
     * 
     * @param servicesController servicesController
     */
    void setServicesController(ServicesController servicesController);

    /**
     * Retorna a classe do controller utilizado por esse servico.
     * 
     * @return a classe do controller utilizado por esse servico
     * @deprecated usar o <code>@Injected</code> para injetar o controller certo
     */
    Class<C> getControllerClass();

    /**
     * Retorna o conjunto de propriedades do servico.
     * 
     * @return o conjunto de propriedades do servico
     */
    TypedScope getServiceProperties();

    /**
     * Seta o conjunto de propriedades do servico.
     * 
     * @param serviceProperties serviceProperties
     */
    void setServiceProperties(TypedScope serviceProperties);

    /**
     * Retorna a localizacao do servico.
     * 
     * @return a localizacao do servico
     */
    String getServiceLocation();

    /**
     * Seta a localizacao do servico.
     * 
     * @param serviceLocation serviceLocation
     */
    void setServiceLocation(String serviceLocation);

    /**
     * Define a pagina desse servico.
     * 
     * @param servicesPage a pagina desse servico.
     */
    void setServicesPage(ServicesPage servicesPage);

    /**
     * Devolve a pagina desse servico.
     * 
     * @return a pagina desse servico.
     */
    ServicesPage getServicesPage();

    /**
     * Cria uma copia do serviço.
     * 
     * @return uma copia do serviço.
     * @throws CloneNotSupportedException se não foi possivel criar uma copia do serviço
     * @deprecated Usar o {@link ServiceFactory} para criar novos servicos
     */
    Service<C> clone() throws CloneNotSupportedException;

    /**
     * Obtém a definição de trasação que este serviço exige para rodar.
     * 
     * @return TransactionDefinition
     */
    TransactionDefinition getTransactionDefinition();
}